﻿/*using System.Collections.Generic;
using System.Linq;
using System.Text.RegularExpressions;
using System.Web;
using System.Web.Mvc;
using System.Web.Routing;

namespace Smarly.Web.RouteConstraints
{
	public static class AreaRegistrationContextExtention
	{
		public static DomainRoute MapDomainRoute(this AreaRegistrationContext context, string name, string domain, string url, object defaults, object constraints = null, string[] namespaces = null)
		{
			if (namespaces == null && context.Namespaces != null)
			{
				namespaces = context.Namespaces.ToArray();
			}

			var result = new DomainRoute(domain, url, defaults, constraints)
			{
				DataTokens = new RouteValueDictionary
					             {
						             {"area", context.AreaName},
						             {"Namespaces", namespaces},
					             }
			};


			// disabling the namespace lookup fallback mechanism keeps this areas from accidentally picking up
			// controllers belonging to other areas
			bool useNamespaceFallback = (namespaces == null || namespaces.Length == 0);
			result.DataTokens["UseNamespaceFallback"] = useNamespaceFallback;

			context.Routes.Add(name, result);

			return result;
		}
	}

	public class DomainRoute : Route
	{
		private Regex domainRegex;
		private Regex pathRegex;

		public DomainRoute(string domain, string url)
			: base(url, new MvcRouteHandler())
		{
			Domain = domain;
		}

		public DomainRoute(string domain, string url, object defaults)
			: base(url, new RouteValueDictionary(defaults), new MvcRouteHandler())
		{
			Domain = domain;
		}

		public DomainRoute(string domain, string url, object defaults, object constraints)
			: base(url, new RouteValueDictionary(defaults), new RouteValueDictionary(constraints), new MvcRouteHandler())
		{
			Domain = domain;
		}

		public DomainRoute(string domain, string url, object defaults, object constraints, RouteValueDictionary dataTokens)
			: base(url, new RouteValueDictionary(defaults), new RouteValueDictionary(constraints), dataTokens, new MvcRouteHandler())
		{
			Domain = domain;
		}

		public string Domain { get; set; }


		#region override

		public override RouteData GetRouteData(HttpContextBase httpContext)
		{
			// Build regex
			domainRegex = CreateRegex(Domain);
			pathRegex = CreateRegex(Url);

			// Request information
			string requestDomain = httpContext.Request.Headers["host"];
			if (!string.IsNullOrEmpty(requestDomain))
			{
				if (requestDomain.IndexOf(":") > 0)
				{
					requestDomain = requestDomain.Substring(0, requestDomain.IndexOf(":"));
				}
			}
			else
			{
				requestDomain = httpContext.Request..;
			}
			string requestPath = httpContext.Request.AppRelativeCurrentExecutionFilePath.Substring(2) +
			                     httpContext.Request.PathInfo;

			// Match domain and route
			Match domainMatch = domainRegex.Match(requestDomain);
			Match pathMatch = pathRegex.Match(requestPath);

			// Route data
			RouteData data = null;
			if (domainMatch.Success && pathMatch.Success)
			{
				data = new RouteData(this, RouteHandler);

				// Add defaults first
				if (Defaults != null)
				{
					foreach (KeyValuePair<string, object> item in Defaults)
					{
						data.Values[item.Key] = item.Value;
					}
				}

				// Iterate matching domain groups
				for (int i = 1; i < domainMatch.Groups.Count; i++)
				{
					Group group = domainMatch.Groups[i];
					if (group.Success)
					{
						string key = domainRegex.GroupNameFromNumber(i);

						if (!string.IsNullOrEmpty(key) && !char.IsNumber(key, 0))
						{
							if (!string.IsNullOrEmpty(group.Value))
							{
								data.Values[key] = group.Value;
							}
						}
					}
				}

				// Iterate matching path groups
				for (int i = 1; i < pathMatch.Groups.Count; i++)
				{
					Group group = pathMatch.Groups[i];
					if (group.Success)
					{
						string key = pathRegex.GroupNameFromNumber(i);

						if (!string.IsNullOrEmpty(key) && !char.IsNumber(key, 0))
						{
							if (!string.IsNullOrEmpty(group.Value))
							{
								data.Values[key] = group.Value;
							}
						}
					}
				}
			}

			return data;
		}

		public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values)
		{
			return base.GetVirtualPath(requestContext, RemoveDomainTokens(values));
		}

		#endregion

		public DomainData GetDomainData(RequestContext requestContext, RouteValueDictionary values)
		{
			// Build hostname
			string hostname = Domain;
			foreach (KeyValuePair<string, object> pair in values)
			{
				hostname = hostname.Replace("{" + pair.Key + "}", pair.Value.ToString());
			}

			// Return domain data
			return new DomainData
			{
				Protocol = "http",
				HostName = hostname,
				Fragment = ""
			};
		}

		private Regex CreateRegex(string source)
		{
			// Perform replacements
			source = source.Replace("/", @"\/?");
			source = source.Replace(".", @"\.?");
			source = source.Replace("-", @"\-?");
			source = source.Replace("{", @"(?<");
			source = source.Replace("}", @">([a-zA-Z0-9_]*))");

			return new Regex("^" + source + "$");
		}

		private RouteValueDictionary RemoveDomainTokens(RouteValueDictionary values)
		{
			Regex tokenRegex = new Regex(@"({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?({[a-zA-Z0-9_]*})*-?\.?\/?");
			Match tokenMatch = tokenRegex.Match(Domain);
			for (int i = 0; i < tokenMatch.Groups.Count; i++)
			{
				Group group = tokenMatch.Groups[i];
				if (group.Success)
				{
					string key = group.Value.Replace("{", "").Replace("}", "");
					if (values.ContainsKey(key))
						values.Remove(key);
				}
			}

			return values;
		}
	}

	public class DomainData
	{
		public string Protocol { get; set; }
		public string HostName { get; set; }
		public string Fragment { get; set; }
	}
}*/